package com.klm.common.config;

import com.baomidou.dynamic.datasource.toolkit.DynamicDataSourceContextHolder;
import com.klm.common.util.DataBaseUtils;
import jakarta.annotation.PostConstruct;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.core.io.support.ResourcePatternResolver;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Component;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;

@Slf4j
@Component
public class DatabaseInitializer {

    @Autowired
    private DataBaseUtils dataBaseUtils;

    @Autowired
    private JdbcTemplate jdbcTemplate;

    @PostConstruct
    public void initializeDatabase() throws IOException {

        if (dataBaseUtils.getLangDbAutoDeploymentEnabled()) {

            // 默认数据源
            String defaultKey = dataBaseUtils.getPrimaryKey();
            log.info("[Trans. plugin] 系统默认数据源: {}", defaultKey);

            // 切换到语言数据源
            String langKey = dataBaseUtils.getLangDbKey();
            langKey = langKey == null ? defaultKey : langKey;
            dataBaseUtils.changeLangDataSource(langKey);

            log.info("[Trans. plugin] 語言資料庫自動初始化開始(START)");
            log.info("[Trans. plugin] 当前使用数据源: {}", DynamicDataSourceContextHolder.peek());
            log.info("[Trans. plugin] 語言資料庫類型: {}", dataBaseUtils.getLangDbType());
            // 自動部署語言資料庫
            String databaseType = dataBaseUtils.getLangDbType();
            if ("mariadb".equals(databaseType)) {
                databaseType = "mysql";
            }
            String filePath = "sql/" + databaseType + "/";
            List<String> fileNames = this.readFileNamesByPath(filePath);
            for (String fileName : fileNames) {
                String fullSql = readLargeSqlFile(filePath + fileName);
                try {
                    String[] sqls = fullSql.split(";");
                    for (String sql : sqls) {
                        jdbcTemplate.execute(sql);
                    }
                    log.info("[Trans. plugin] 执行自动初始化SQL文件 [{}] 成功",fileName);
                } catch (Exception e) {
                    log.error("[Trans. plugin] 执行自动初始化SQL文件 [{}] 失败",fileName,e);
                }
            }
            // 切换回默认数据源
            dataBaseUtils.changeLangDataSource(defaultKey);

            log.info("[Trans. plugin] 語言資料庫自動初始化結束(END)");
        } else {
            log.info("[Trans. plugin] 語言資料庫未開啟或自動部署未開啟");
        }
    }

    /**
     * 根据路径读取文件路径
     * @param locationPath 路径
     * @return 文件路径列表
     * @throws IOException  IO异常
     */
    public List<String> readFileNamesByPath(String locationPath) throws IOException {
        // 创建ResourcePatternResolver的实例
        ResourcePatternResolver patternResolver = new PathMatchingResourcePatternResolver();

        // 通过ResourcePatternResolver查找资源 SQL文件的扩展名是.sql
        Resource[] resources = patternResolver.getResources(locationPath + "*.sql");
        log.info("[Trans. plugin] ResourcePattern: {}", locationPath + "*.sql");
        List<String> filePaths = new ArrayList<>();
        // 遍历资源
        for (Resource resource : resources) {
            // 检查资源是否存在
            if (resource.exists()) {
                filePaths.add(resource.getFilename());
            } else {
                System.out.println("Resource not found: " + resource.getFilename());
            }
        }
        return filePaths;
    }

    /**
     * 根据文件名 读取大型SQL文件
     * @param filePath 文件路径
     * @return SQL内容
     */
    public static String readLargeSqlFile(String filePath) {
        StringBuilder sqlContent = new StringBuilder();
        try {
            // 创建Resource对象，指向类路径下的文件
            Resource resource = new ClassPathResource(filePath);
            // 确保文件存在
            if (resource.exists()) {
                // 获取文件的输入流
                try (InputStream inputStream = resource.getInputStream();
                     BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, StandardCharsets.UTF_8))) {

                    reader.lines().forEach(sqlContent::append);
                }
            } else {
                throw new IllegalArgumentException("[Trans. plugin] The SQL file does not exist: " + filePath);
            }
        } catch (Exception e) {
            // 处理异常
            log.error("[Trans. plugin] Failed to read SQL file: {}", filePath, e);
        }
        return sqlContent.toString();
    }
}
